<template>
  <div class="page">
    <div class="context">
      <div class="title_1" style="cursor: pointer" @click.stop="handleToggleTags">
        <span v-if="quanOpt.updating">修改全案</span>
        <span v-else>创建全案</span>
        <i v-if="chooseTags.dataLoading" class="el-icon-loading"></i>
        <i v-else-if="chooseTags.popMe" class="el-icon-arrow-down"></i>
        <i v-else class="el-icon-arrow-right"></i>
      </div>
      <div v-if="chooseTags.popMe">
        <!-- 基础标签 Tag V1 -->
        <div v-for="item in clerkBaseTag" class="title_1_ctx2">
          <table style="margin-left: -2px">
            <tr style="vertical-align: top">
              <td>
                <div class="title_2">
                  <div class="title_icon"></div>
                  <div class="title_name">{{ item.title }}</div>
                </div>
              </td>
              <td>
                <div class="tag_list">
                  <div v-for="tag in item.options" class="tag_item">
                    <div class="tag_name">
                      <span>{{ tag.name }}</span>
                      <i class="el-icon-plus tag_add" @click.stop="expAddTagV1(item.value, tag.value, tag.name)"></i>
                    </div>
                  </div>
                </div>
              </td>
            </tr>
          </table>
        </div>
        <!-- Tag V2 -->
        <div v-for="item in gategoryTags" class="title_1_ctx2">
          <table style="margin-left: -2px">
            <tr style="vertical-align: top">
              <td>
                <div class="title_2">
                  <div class="title_icon"></div>
                  <div class="title_name">{{ item.name }}</div>
                </div>
              </td>
              <td>
                <div class="tag_list">
                  <div v-for="tag in item.tags" class="tag_item">
                    <div class="tag_name">
                      <span>{{ tag.tag }}</span>
                      <i class="el-icon-plus tag_add" @click.stop="expAddTagV2(tag)"></i>
                    </div>
                  </div>
                </div>
              </td>
            </tr>
          </table>
        </div>

        <!--已选择的标签-->
        <div class="title_1_ctx2" style="padding: 5px 10px 0 0">
          <table style="margin-left: -2px">
            <tr style="vertical-align: top">
              <td>
                <div class="title_2">
                  <div style="width: 4px; height: 13px"></div>
                  <div class="title_name" style="color: #606266; font-weight: 700">标签组合</div>
                </div>
              </td>
              <td>
                <tag-expression ref="refTagExpression" style="width: 800px"></tag-expression>
              </td>
            </tr>
            <tr>
              <td colspan="2"></td>
            </tr>
          </table>
        </div>

        <!--添加全案信息-->
        <div class="context" style="margin-top: 20px; position: relative; padding-bottom: 25px">
          <div class="title_1">全案信息</div>
          <table class="act_info" cellspacing="10">
            <tr>
              <td style="width: 13%">
                <div class="title_1_ctx1">
                  <div class="title_2">
                    <div class="title_icon"></div>
                    <div class="title_name">全案类型</div>
                  </div>
                  <div class="title_1_ctx1_1">
                    <table>
                      <tr>
                        <td>
                          <el-radio-group v-model="quanVo.scheme" class="tag_list" :disabled="quanOpt.updating">
                            <el-radio class="tag_item" :label="1">沙龙</el-radio>
                            <el-radio class="tag_item" :label="2">客情</el-radio>
                            <el-radio class="tag_item" :label="3">生日</el-radio>
                          </el-radio-group>
                        </td>
                      </tr>
                    </table>
                  </div>
                </div>
              </td>
              <td style="width: 20%">
                <div class="title_1_ctx1">
                  <div class="title_2">
                    <div class="title_icon"></div>
                    <div class="title_name">全案简介</div>
                  </div>
                  <div class="title_1_ctx1_1" style="width: 100%">
                    <el-input
                      v-model="quanVo.brief"
                      type="textarea"
                      maxlength="64"
                      show-word-limit
                      :autosize="{ minRows: 2, maxRows: 3 }"
                      placeholder="请输入全案简介"></el-input>
                  </div>
                </div>
              </td>
              <td style="width: 20%">
                <div class="title_1_ctx1">
                  <div class="title_2">
                    <div class="title_icon"></div>
                    <div class="title_name">全案方案</div>
                  </div>
                  <div class="title_1_ctx1_1">
                    <el-upload
                      action="/"
                      :before-upload="handleFileBeforeUpload"
                      :on-progress="handleFileUploading"
                      :on-success="handleFileUploadOk"
                      :on-error="handleFileUploadError"
                      :http-request="handleFileUpload"
                      :file-list="quanFileList"
                      :auto-upload="true"
                      :multiple="false"
                      :disabled="quanOpt.proposalUploading"
                      accept=".txt,.pdf">
                      <el-button size="small" type="primary">点击上传</el-button>
                      <div slot="tip" class="el-upload__tip">只能上传 pdf/txt 文件, 且不超过20M</div>
                    </el-upload>
                  </div>
                </div>
              </td>
              <td style="width: 20%; vertical-align: bottom">
                <div class="commit">
                  <el-button v-if="quanOpt.creating" type="primary" size="small" disabled icon="el-icon-loading">
                    <span v-if="quanOpt.updating">确认修改</span>
                    <span v-else>确认创建</span>
                  </el-button>
                  <el-button v-else type="primary" size="small" @click.stop="handleCreateQuanAn">
                    <span v-if="quanOpt.updating">确认修改</span>
                    <span v-else>确认创建</span>
                  </el-button>
                </div>
              </td>
            </tr>
          </table>
        </div>
      </div>
    </div>

    <div>
      <div class="title_1_ctx1">
        <div class="title_1_ctx2">
          <span>类型：</span>
          <el-select v-model="quanTable.searchScheme" size="mini" clearable style="width: 80px">
            <el-option label="沙龙" :value="1"></el-option>
            <el-option label="客情" :value="2"></el-option>
            <el-option label="生日" :value="3"></el-option>
          </el-select>
          <span>简介：</span>
          <el-input
            v-model="quanTable.searchBrief"
            size="mini"
            clearable
            style="width: 180px"
            placeholder="模糊查询全案简介"
            prefix-icon="el-icon-search"></el-input>
          <el-button v-if="quanTable.dataListLoading" size="mini" type="success" disabled icon="el-icon-loading">
            搜索
          </el-button>
          <el-button v-else size="mini" type="success" @click.stop="loadQuanAnList">搜索</el-button>
        </div>
        <div class="title_1_ctx1_1" style="width: 82vw">
          <el-table
            ref="refTable"
            v-loading="quanTable.dataListLoading"
            :data="quanTable.dataList"
            element-loading-text="Loading"
            border
            fit
            highlight-current-row>
            <el-table-column fixed label="类型" align="center" width="80">
              <template slot-scope="{ row }">
                <div v-if="row.scheme === 1" style="color: #724eff">沙龙</div>
                <div v-if="row.scheme === 2" style="color: #f29339">客情</div>
                <div v-if="row.scheme === 3" style="color: #469b78">生日</div>
              </template>
            </el-table-column>
            <el-table-column label="状态" align="center" width="80">
              <template slot-scope="{ row }">
                <div v-if="row.sts === 3" style="color: rgb(255, 159, 70)">已下架</div>
                <div v-if="row.sts === 2" style="color: #67c23a">已上架</div>
                <div v-if="row.sts === 1">创建中</div>
                <div v-if="row.sts === 0">未知</div>
              </template>
            </el-table-column>
            <el-table-column
              prop="brief"
              label="简介"
              align="center"
              width="600"
              show-overflow-tooltip></el-table-column>
            <el-table-column label="方案" align="center" width="80">
              <template slot-scope="{ row }">
                <div v-if="row.proposal">已上传</div>
                <div v-else>未上传</div>
              </template>
            </el-table-column>
            <el-table-column prop="createDate" label="创建时间" align="center" width="120">
              <template slot-scope="{ row }">
                {{ row.createDate ? row.createDate.substring(0, 10) : '' }}
              </template>
            </el-table-column>
            <el-table-column fixed="right" label="操作" align="center" width="320">
              <template slot-scope="{ row }">
                <el-button
                  type="info"
                  size="mini"
                  plain
                  :disabled="!row.proposal"
                  @click.stop="handleShowProposal(row)">
                  查看方案
                </el-button>
                <el-button
                  v-if="row.sts == 1"
                  type="primary"
                  size="mini"
                  plain
                  :disabled="quanOpt.updating"
                  @click.stop="handleUpdateQuanAn(row)">
                  修改
                </el-button>
                <el-button
                  v-if="row.sts == 1"
                  type="success"
                  size="mini"
                  plain
                  :disabled="quanOpt.updating"
                  @click.stop="handlePublish(row)">
                  上架
                </el-button>
                <el-button
                  v-if="row.sts == 2"
                  type="warning"
                  size="mini"
                  plain
                  :disabled="quanOpt.updating"
                  @click.stop="handleReclaim(row)">
                  下架
                </el-button>
                <el-button
                  v-if="row.delable"
                  type="danger"
                  size="mini"
                  plain
                  :disabled="quanOpt.updating"
                  @click.stop="handleDeleteQuanAn(row)">
                  删除
                </el-button>
                <span v-if="row.sts === 3 && !row.delable" style="color: #e6a23c; margin-left: 3px">下架24h可删</span>
              </template>
            </el-table-column>
          </el-table>

          <pagination
            v-show="quanTable.total > 0"
            :total="quanTable.total"
            :page.sync="quanTable.pageParam.page"
            :limit.sync="quanTable.pageParam.limit"
            @pagination="loadQuanAnList"></pagination>
        </div>
      </div>
    </div>
  </div>
</template>

<script>
import * as apiSts from '@/api/_com_';
// 引入后端 API
import { getAllBaseTagsNoCount } from '@/api/activity';
import * as qaApi from '@/api/quanan';
// 引入自定义组件
import Pagination from '@/components/Pagination';
import TagGategory from '@/utils/enum/tag-gategorys';
import TagExpression from './exp2.vue';
import { ExpresionType } from './expression';
// 引入第三方组件
import { MessageBox } from 'element-ui';
import { mapGetters } from 'vuex';

// 基础标签：这些标签都是 clerk 表的属性, value 要用 clerk 表的列名
const ClerkBaseTag = [
  {
    title: '消费等级',
    value: 'grade',
    options: [
      { name: '未定', value: 0 },
      { name: 'C级', value: 1 },
      { name: 'B级', value: 2 },
      { name: 'A级', value: 3 },
      { name: 'S级', value: 4 },
    ],
  },
  {
    title: '信任状态',
    value: 'trust2',
    options: [
      { name: '未破冰', value: 1 },
      { name: '已破冰', value: 2 },
      { name: '已信任', value: 3 },
    ],
  },
  {
    title: '运营状态',
    value: 'dengji',
    options: [
      { name: '正常', value: 0 },
      { name: '预警', value: 1 },
      { name: '失速', value: 2 },
      { name: '放弃', value: 3 },
    ],
  },
  {
    title: '消费能力',
    value: 'bg2',
    options: [
      { name: '超有钱', value: 0 },
      { name: '有钱', value: 1 },
      { name: '普通', value: 2 },
      { name: '没钱', value: 3 },
    ],
  },
  {
    title: '需求大小',
    value: 'demand_level',
    options: [
      { name: '未设置', value: 0 },
      { name: '小', value: 1 },
      { name: '中', value: 2 },
      { name: '大', value: 3 },
    ],
  },
  {
    title: '重点',
    value: 'noble',
    options: [
      { name: '非重点', value: 0 },
      { name: '重点', value: 2 },
    ],
  },
  {
    title: '年龄', // 年龄是特殊的，age 属性在 clerk 表中不存在，需要通过生日来计算
    value: 'age',
    options: [
      { name: '20岁以下', value: 1 },
      { name: '20-30岁', value: 2 },
      { name: '30-40岁', value: 3 },
      { name: '40-50岁', value: 4 },
      { name: '50-60岁', value: 5 },
      { name: '60岁以上', value: 6 },
    ],
  },
];

const EmptyQuanAn = {
  id: undefined,
  scheme: null, // 全案类型
  sts: 0,
  brief: null, // 简单的计划(文字描述)
  proposal: null, // 详细的计划(文档或者图片)
  tagExpression: '', // 标签表达式
  delable: false,
  createDate: '',
};

export default {
  name: 'TagQuanAn',
  components: { Pagination, ['tag-expression']: TagExpression },
  data() {
    return {
      clerkBaseTag: ClerkBaseTag,
      gategoryTags: [],
      chooseTags: {
        // 全案标签筛选区域
        popMe: false,
        dataLoading: false,
      },
      quanFileList: [],
      quanTable: {
        // 全案列表
        dataList: [],
        dataListLoading: false,
        total: 0,
        pageParam: { page: 1, limit: 10 },
        searchBrief: '',
        searchScheme: undefined,
      },
      quanOpt: {
        // 创建全案区域
        proposalUploading: false,
        creating: false,
        updating: false,
      },
      quanVo: Object.assign({}, EmptyQuanAn),
    };
  },
  computed: {
    ...mapGetters(['name', 'id', 'deptId']),
  },
  created() {
    this.loadAllTags();
  },
  mounted() {
    this.loadQuanAnList();
  },
  methods: {
    handleToggleTags() {
      if (this.chooseTags.dataLoading) {
        return;
      }
      this.quanVo = Object.assign({}, EmptyQuanAn);
      this.chooseTags.popMe = !this.chooseTags.popMe;
      this.quanOpt.updating = false;
    },
    handleFileBeforeUpload(file) {
      const allowFileTypes = ['txt', 'pdf'];
      const fileType = file.name.split('.').pop().toLowerCase();
      if (allowFileTypes.indexOf(fileType) === -1) {
        MessageBox.alert('只能上传指定格式的文件!');
        return false;
      }
      return true;
    },
    handleFileUploading(event, file, fileList) {
      this.quanOpt.proposalUploading = true;
    },
    handleFileUploadOk(res, file, fileList) {
      this.quanOpt.proposalUploading = false;
      this.$message({
        message: '文件上传完成',
        type: 'success',
      });
    },
    handleFileUploadError(err, file, fileList) {
      this.quanOpt.proposalUploading = false;
    },
    handleFileUpload: async function (options) {
      const file = options.file;
      const formData = new FormData();
      formData.append('file', file);
      await qaApi
        .uploadProposal(formData)
        .then(res => {
          if (res.data.status !== apiSts.ResponseOK) {
            if (res.data.message) {
              MessageBox.alert('文件上传失败: ' + res.data.message);
            } else {
              MessageBox.alert('文件上传失败!');
            }
            return;
          }
          this.quanVo.proposal = res.data.data;
        })
        .catch(err => {
          MessageBox.alert('文件上传失败!');
        })
        .finally(() => {
          this.quanOpt.proposalUploading = false;
        });
    },
    handleCreateQuanAn: async function () {
      if (this.quanOpt.creating) {
        return;
      }
      if (!this.quanVo.scheme) {
        this.$message.error('请选择全案类型');
        return;
      }
      if (this.quanVo.brief) {
        this.quanVo.brief = this.quanVo.brief.trim();
      }
      if (!this.quanVo.brief) {
        this.$message.error('请填写全案简介');
        return;
      }
      const expStr = this.$refs.refTagExpression.getExpressionStr();
      if (!expStr) {
        this.$message.error('请编辑标签逻辑表达式');
        return;
      }
      this.quanVo.tagExpression = expStr;
      this.quanOpt.creating = true;
      const errAlertMsg = '保存全案失败';
      await qaApi
        .saveQuanAn(this.quanVo)
        .then(res => {
          if (res.data.status !== apiSts.ResponseOK) {
            if (res.data.message) {
              MessageBox.alert(res.data.message);
            } else {
              MessageBox.alert(errAlertMsg);
            }
            return;
          }
          this.handleToggleTags();
          this.loadQuanAnList();
          MessageBox.alert('保存成功');
        })
        .catch(err => {
          console.log('saveQuanAn', err);
          MessageBox.alert(errAlertMsg);
        })
        .finally(() => {
          this.quanOpt.creating = false;
        });
    },
    handleShowProposal: async function (row) {
      if (!row.proposal) {
        this.$message.error('该全案没有上传方案');
        return;
      }
      // pdf 或者 txt
      const proposalUrl = `/pub/quanan/proposal?relativePath=${row.proposal}`;
      window.open(proposalUrl, '_blank');
    },
    handleUpdateQuanAn: async function (row) {
      if (this.quanOpt.updating) {
        return;
      }
      this.quanOpt.updating = true;
      this.quanVo = Object.assign({}, row);
      this.chooseTags.popMe = true;
      await this.$nextTick();
      const expList = this.$refs.refTagExpression.expressionFromStr(row.tagExpression);
      // 设置标签对应的名字
      const setTagName = list => {
        list.forEach(exp => {
          if (exp.type === ExpresionType.UnaryOperator || exp.type === ExpresionType.BinaryOperator) {
            return;
          }
          if (exp.type === ExpresionType.ImmediateValue) {
            exp.name = this.getTagNameByCode(exp.code);
            return;
          }
          if (exp.type === ExpresionType.Parentheses) {
            setTagName(exp.children);
          }
        });
      };
      if (expList && expList.length > 0) {
        setTagName(expList);
      }
      this.$refs.refTagExpression.setExpressionList(expList);
    },
    handleDeleteQuanAn: async function (row) {
      const errAlertMsg = '删除失败';
      this.$confirm(`全案简介: [${row.brief}], 确定要删除吗?`, '删除提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning',
      })
        .then(() =>
          qaApi
            .delQuanAn(row.id)
            .then(res => {
              if (res.data.status !== apiSts.ResponseOK) {
                if (res.data.message) {
                  MessageBox.alert(res.data.message);
                } else {
                  MessageBox.alert(errAlertMsg);
                }
                return;
              }
              this.loadQuanAnList();
            })
            .catch(err => {
              console.error(err);
              MessageBox.alert(errAlertMsg);
            })
        )
        .catch();
    },
    handlePublish: async function (row) {
      if (!row.proposal) {
        MessageBox.alert('还未上传方案, 不能上架');
        return;
      }
      const errAlertMsg = '上架失败';
      this.$confirm(`全案简介: [${row.brief}], 确定要上架吗?`, '上架提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning',
      })
        .then(() =>
          qaApi
            .publishQuanAn(row.id)
            .then(res => {
              if (res.data.status !== apiSts.ResponseOK) {
                if (res.data.message) {
                  MessageBox.alert(res.data.message);
                } else {
                  MessageBox.alert(errAlertMsg);
                }
                return;
              }
              this.loadQuanAnList();
            })
            .catch(err => {
              console.error(err);
              MessageBox.alert(errAlertMsg);
            })
        )
        .catch();
    },
    handleReclaim: async function (row) {
      const errAlertMsg = '下架失败';
      this.$confirm(`全案简介: [${row.brief}], 确定要下架吗?`, '下架提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning',
      })
        .then(() =>
          qaApi
            .reclaimQuanAn(row.id)
            .then(res => {
              if (res.data.status !== apiSts.ResponseOK) {
                if (res.data.message) {
                  MessageBox.alert(res.data.message);
                } else {
                  MessageBox.alert(errAlertMsg);
                }
                return;
              }
              this.loadQuanAnList();
            })
            .catch(err => {
              console.error(err);
              MessageBox.alert(errAlertMsg);
            })
        )
        .catch();
    },
    getTagNameByCode(code) {
      if (!code) {
        return '';
      }
      if (code[0] === '#') {
        const tmp = code.substring(1).split('@');
        const attrName = tmp[0];
        const attrValue = tmp[1];
        const tag = ClerkBaseTag.find(x => x.value === attrName);
        if (tag) {
          const tagOption = tag.options.find(x => x.value == attrValue);
          if (tagOption && tagOption.name) {
            return tagOption.name;
          }
        }
      } else if (code[0] === '@') {
        const attrName = code.substring(1);
        let tagName = undefined;
        this.gategoryTags.some(x => {
          x.tags.some(y => {
            if (y.name === attrName) {
              tagName = y.tag;
              return true;
            }
            return false;
          });
          return !!tagName;
        });
        if (tagName) {
          return tagName;
        }
      }
      return '[未知]';
    },
    /**
     * 将基础标签添加到表达式中
     * <p>
     * 这些属性都保存在 clerk 表中，
     *
     * @param {string} tagAttr  在 clerk 表中的列名
     * @param {string} tagValue 值
     * @param {string} tagName  标签名称
     */
    expAddTagV1: async function (tagAttr, tagValue, tagName) {
      const exp = { name: tagName, code: `#${tagAttr}@${tagValue}` };
      if (this.$refs.refTagExpression) {
        this.$refs.refTagExpression.addTagExp(exp);
      }
    },
    /**
     * 将基 V2 签添加到表达式中
     * <p>
     * 这些属性都保存在 t_clerk_tags 表中
     *
     * @param {Object} tag 标签 V2
     */
    expAddTagV2: async function (tag) {
      const exp = { name: tag.tag, code: `@${tag.name}` };
      if (this.$refs.refTagExpression) {
        this.$refs.refTagExpression.addTagExp(exp);
      }
    },
    loadAllTags: async function () {
      if (this.chooseTags.dataLoading) {
        return;
      }
      this.chooseTags.dataLoading = true;
      this.gategoryTags.splice(0, this.gategoryTags.length);
      const errAlertMsg = '查询标签失败';
      await getAllBaseTagsNoCount()
        .then(res => {
          if (res.data.status !== apiSts.ResponseOK) {
            if (res.data.message) {
              MessageBox.alert(res.data.message);
            } else {
              MessageBox.alert(errAlertMsg);
            }
            return;
          }
          const ret = res.data.data;
          const gategory = ret.gategory;
          const gategoryTags = ret.gategoryTags;
          const tmpList = [];
          for (const gk in gategory) {
            if (!gategory.hasOwnProperty(gk)) {
              continue;
            }
            if (TagGategory.TAG_101_200_XF_CENG_JING.id == gk || TagGategory.TAG_1_100_XING_QU.id == gk) {
              // 过滤 曾经消费, 兴趣标签
              continue;
            }
            const tags = gategoryTags[gk];
            if (!tags || !tags.length) {
              continue;
            }
            tmpList.push({ code: gk, name: gategory[gk], tags: tags });
          }
          tmpList.sort((a, b) => Number.parseInt(a.code) - Number.parseInt(b.code));
          this.gategoryTags.push(...tmpList);
        })
        .catch(err => {
          console.error(err);
          MessageBox.alert(errAlertMsg);
        })
        .finally(() => {
          this.chooseTags.dataLoading = false;
        });
    },
    loadQuanAnList: async function () {
      if (this.quanTable.dataListLoading) {
        return;
      }
      this.quanTable.dataListLoading = true;
      const errAlertMsg = '查询全案列表失败';

      const params = {};
      params.pageNumber = this.quanTable.pageParam.page;
      params.pageSize = this.quanTable.pageParam.limit;
      if (this.quanTable.searchBrief) {
        params.brief = this.quanTable.searchBrief;
      }
      if (this.quanTable.searchScheme) {
        params.scheme = this.quanTable.searchScheme;
      }
      await qaApi
        .getQuanAnPage(params)
        .then(res => {
          if (res.data.status !== apiSts.ResponseOK) {
            if (res.data.message) {
              MessageBox.alert(res.data.message);
            } else {
              MessageBox.alert(errAlertMsg);
            }
            return;
          }
          if (res.data.data) {
            this.quanTable.dataList = res.data.data.records;
            this.quanTable.total = res.data.data.total;
          }
        })
        .catch(e => {
          console.log('getQuanAnPage', e);
          MessageBox.alert(errAlertMsg);
        })
        .finally(() => {
          this.quanTable.dataListLoading = false;
        });
    },
  },
};
</script>

<style lang="scss" scoped>
@import '@/assets/css/scrollbar.scss';
$font-family: 微软雅黑 宋体 思源黑体 Noto Sans SC-Medium;
$title-width: 100px;
$tag-height: 17px;
$tag-line-height: 17px;

::v-deep .el-table td {
  padding: 5px 0;
  min-width: 0;
  box-sizing: border-box;
  text-overflow: ellipsis;
  vertical-align: middle;
  position: relative;
}

.page {
  position: relative;
  width: 100%;
  height: 1920px;
  padding: 5px 10px 0 10px;
  font-family: $font-family;
  background-color: #f8f8fa;
  border-radius: 0px 0px 0px 0px;

  .context {
    width: 100%;
    padding: 5px 10px 0 0;
    display: flex;
    flex-direction: column;
    align-items: flex-start;
    justify-content: center;
    gap: 20px;
  }

  .title_1 {
    font-family: $font-family;
    font-size: 0.111rem;
    font-weight: bold;
    line-height: 18px;
    letter-spacing: 0px;
    font-variation-settings: 'opsz' auto;
    color: #724eff;
    letter-spacing: 1px;
  }

  .title_1_ctx1 {
    width: 100%;
    padding: 0px 0px 0px 0px;
    display: flex;
    flex-direction: column;
    align-items: flex-start;
    justify-content: center;
    gap: 10px;

    .title_1_ctx1_1 {
      display: block;
      text-align: left;

      .act_times {
        display: flex;
        flex-direction: row;
        align-items: center;
        justify-content: space-between;
      }
    }
  }

  .title_1_ctx1 tr {
    margin-top: 5px;
  }

  .title_1_ctx2 {
    width: 100%;
    padding: 0px 0px 0px 0px;
    display: flex;
    flex-direction: row;
    align-items: center;
    justify-content: flex-start;
    gap: 5px;
  }

  .title_2 {
    width: $title-width;
    height: 100%;
    display: flex;
    flex-direction: row;
    justify-content: flex-start;
    align-items: center;
    gap: 5px;

    .title_icon {
      width: 4px;
      height: 13px;
      background: #766aff;
      background-position: left bottom;
      background-repeat: no-repeat;
      background-size: 100% 100%;
    }

    .title_name {
      font-family: $font-family;
      font-size: 16px;
      font-weight: 550;
      line-height: 22px;
      letter-spacing: 0px;
      font-variation-settings: 'opsz' auto;
      color: #333333;
      letter-spacing: 1px;

      .no_flex {
        display: inline;
        margin-left: 15px;
      }
    }
  }
}

.tag_list {
  width: 100%;
  height: auto;
  padding: 3px 0 0 0;
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  justify-content: flex-start;
  align-items: center;
  gap: 10px;
}

.tag_item {
  margin: 0 0 0 0;
  display: flex;
  flex-direction: row;
  align-items: center;
  justify-content: flex-start;
  gap: 0px;
}

.tag_name {
  width: auto;
  height: $tag-height;
  line-height: $tag-line-height;
  padding: 1px 3px;
  text-align: center;
  font-size: 14px;
  font-weight: normal;
  line-height: 17px;
  letter-spacing: 0px;
  font-variation-settings: 'opsz' auto;
  font-feature-settings: 'kern' on;
  color: #666666;
  border: 1px dashed rgb(207, 155, 244);
  border-radius: 3px;

  .tag_add {
    margin-left: 5px;
    color: #766aff;
    cursor: pointer;
  }
}

.act_info td {
  width: 35%;
  vertical-align: top;
}

.commit {
  position: relative;
  top: 20px;
  right: 20px;
}
</style>
